package com.qys.livesMall.anchor.service.impl;

import com.baomidou.mybatisplus.core.toolkit.CollectionUtils;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.google.common.collect.Lists;
import com.google.common.collect.Maps;
import com.qys.livesMall.anchor.constants.RedisConstant;
import com.qys.livesMall.anchor.mapper.LivesRoomAdminMapper;
import com.qys.livesMall.anchor.model.dto.lives.app.BanUserDTO;
import com.qys.livesMall.anchor.model.entity.AnchorLivesRoom;
import com.qys.livesMall.anchor.model.entity.AnchorLivesSession;
import com.qys.livesMall.anchor.model.entity.LivesRoomAdmin;
import com.qys.livesMall.anchor.service.AnchorLivesRoomService;
import com.qys.livesMall.anchor.service.AnchorLivesSessionService;
import com.qys.livesMall.anchor.service.LivesRoomAdminService;
import com.qys.livesMall.app.user.service.AppUserConcernService;
import com.qys.livesMall.app.user.utils.TencentCloudIm;
import com.qys.livesMall.cache.RedisCache;
import com.qys.livesMall.common.exception.QysException;
import com.qys.livesMall.framework.utils.SecurityUtils;
import jakarta.annotation.Resource;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Service;

import java.time.Instant;
import java.time.ZoneId;
import java.util.HashMap;
import java.util.List;
import java.util.concurrent.TimeUnit;
import java.util.stream.Collectors;

/**
 * 直播间管理员表(LivesRoomAdmin)表服务实现类
 *
 * @author makejava
 * @since 2023-09-12 10:02:05
 */
@Service("livesRoomAdminService")
@Slf4j
public class LivesRoomAdminServiceImpl extends ServiceImpl<LivesRoomAdminMapper, LivesRoomAdmin> implements LivesRoomAdminService {

    @Resource
    private AnchorLivesRoomService livesRoomService;
    @Resource
    private AnchorLivesSessionService livesSessionService;
    @Resource
    private TencentCloudIm tencentCloudIm;
    @Resource
    private RedisCache redisCache;
    @Resource
    private AppUserConcernService appUserConcernService;

    /**
     * 设置直播间管理员
     *
     * @param userId 用户id
     */
    @Override
    public void setAdmin(Long userId) {

        Long anchorUserId = SecurityUtils.getUserId();

        //1、判断主播是否存在
        AnchorLivesRoom room = livesRoomService.getRoomByUserId(anchorUserId);
        if(room == null){
            throw new QysException("Permission Denied");
        }

        //2.获取房管信息
        LivesRoomAdmin admin = baseMapper.selectOne(Wrappers.<LivesRoomAdmin>lambdaQuery().eq(LivesRoomAdmin::getLivesRoomId, room.getId()).eq(LivesRoomAdmin::getUserId, userId));
        if(admin != null){
            //取消房管
            baseMapper.deleteById(admin.getId());
        } else {
            //设置房管
            LivesRoomAdmin livesRoomAdmin = new LivesRoomAdmin();
            livesRoomAdmin.setLivesRoomId(room.getId());
            livesRoomAdmin.setUserId(userId);
            baseMapper.insert(livesRoomAdmin);
        }
    }

    /**
     * 判断用户是否是直播间管理员
     *
     * @param liveRoomNumber 房间编号
     * @param userId 用户id
     * @return
     */
    @Override
    public Boolean isRoomAdmin(String liveRoomNumber, Long userId) {
        if(userId == null){
            userId = SecurityUtils.getUserId();
        }

        AnchorLivesRoom anchorLivesRoom = livesRoomService.queryByRoomNum(liveRoomNumber);
        if(anchorLivesRoom == null){
            throw new QysException("liveRoomNumber error");
        }

        //判断是否是自己的直播间
        AnchorLivesRoom room = livesRoomService.getRoomByUserId(userId);
        if(room != null && room.getLivesRoomNum().equals(liveRoomNumber)){
            return Boolean.TRUE;
        }

        Long count = baseMapper.selectCount(Wrappers.<LivesRoomAdmin>lambdaQuery().eq(LivesRoomAdmin::getLivesRoomId, anchorLivesRoom.getId()).eq(LivesRoomAdmin::getUserId, userId));
        return count == 0 ? Boolean.FALSE : Boolean.TRUE;
    }

    /**
     * 封禁用户
     *
     * @param dto
     */
    @Override
    public void banUser(BanUserDTO dto) {
        Boolean admin = this.isRoomAdmin(dto.getLivesRoomNumber(), null);
        if(!admin){
            throw new QysException("Permission Denied");
        }

        boolean ok = tencentCloudIm.banGroupMember(dto.getLivesRoomNumber(), Lists.newArrayList(String.valueOf(dto.getUserId())), 3600);
        if(ok){
            dto.setCreateBy(SecurityUtils.getUsername());
            baseMapper.banUser(dto);
        } else {
            throw new QysException("banUser fail");
        }
    }

    @Override
    public Boolean isBan(Long livesSessionId, Long userId) {
        int count = baseMapper.userIsban(livesSessionId, userId);
        return count > 0 ? Boolean.TRUE : Boolean.FALSE;
    }

    @Override
    public Integer forbidSendMsg(Long groupId, Integer type) {

        //判断是否是主播
        AnchorLivesRoom room = livesRoomService.getRoomByUserId(SecurityUtils.getUserId());
        if(room == null){
            throw new QysException("Permission Denied");
        }

        //获取主播的当前直播场次
        AnchorLivesSession livesSession = livesSessionService.getIsStarted(room.getId());
        if(livesSession == null){
            throw new QysException("no room living");
        }

        //获取当场直播间禁言状态
        Integer cacheStatus = this.getForbidSendMsgStatus(livesSession.getId());


        if(0 == type){

            //1、之前是否设置过禁言，先取消
            List<String> groupMutedAccount = tencentCloudIm.getGroupMutedAccount(String.valueOf(groupId));
            if(CollectionUtils.isNotEmpty(groupMutedAccount)){
                for (List<String> list : Lists.partition(groupMutedAccount, 500)) {
                    tencentCloudIm.bannedGroupMember(String.valueOf(groupId), 0, list);
                }
            }

            //2、打开所有人发言
            HashMap<String, String> map = Maps.newHashMap();
            map.put("MuteAllMember", "Off");
            tencentCloudIm.modifyGroupInfo(String.valueOf(groupId), map, false);

        } else if(1 == type){

            //打开全局禁言
            HashMap<String, String> map = Maps.newHashMap();
            map.put("MuteAllMember", "On");
            tencentCloudIm.modifyGroupInfo(String.valueOf(groupId), map, false);

        } else if (Lists.newArrayList(2,3).contains(type)) {

            //1、之前是否打开全局禁言，先关闭全局禁言
            if(cacheStatus == 1){
                HashMap<String, String> map = Maps.newHashMap();
                map.put("MuteAllMember", "Off");
                tencentCloudIm.modifyGroupInfo(String.valueOf(groupId), map, false);
            }

            //2、之前是否设置过禁言，先取消
            List<String> groupMutedAccount = tencentCloudIm.getGroupMutedAccount(String.valueOf(groupId));
            if(CollectionUtils.isNotEmpty(groupMutedAccount)){
                for (List<String> list : Lists.partition(groupMutedAccount, 500)) {
                    tencentCloudIm.bannedGroupMember(String.valueOf(groupId), 0, list);
                }
            }

            //3、查询用户
            List<String> userList = Lists.newArrayList();
            if(2 == type){
                userList = baseMapper.queryMyUnfollowedUser(SecurityUtils.getUserId());
                log.info("直播间禁言，查询到我关注的人：{}", userList);
            } else if(3 == type){
                userList = baseMapper.queryNotFollowMeUser(SecurityUtils.getUserId());
                log.info("直播间禁言，查询到关注我的人：{}", userList);
            }

            //4、IM单次请求最大支持500个用户
            for (List<String> list : Lists.partition(userList, 500)) {
                tencentCloudIm.bannedGroupMember(String.valueOf(groupId), Integer.MAX_VALUE , list);
            }
        }

        //处理缓存（当前直播场次禁言状态）
        redisCache.setCacheObject(RedisConstant.LIVE_DISABLE_SEND_MSG + livesSession.getId(), type, 60L, TimeUnit.MINUTES);

        return type;

    }

    @Override
    public Integer getForbidSendMsgStatus(Long sessionId) {
        Integer cacheObject = redisCache.getCacheObject(RedisConstant.LIVE_DISABLE_SEND_MSG + sessionId);
        return  cacheObject == null ? 0 : cacheObject;
    }

    @Override
    public Boolean isForbidSendMsg(String liveRoomNumber, Long userId) {

        userId = userId == null ? SecurityUtils.getUserId() : userId;

        List<String> mutedAccount = tencentCloudIm.getGroupMutedAccount(liveRoomNumber);
        if(mutedAccount.contains(String.valueOf(userId))){
            return Boolean.TRUE;
        } else {
            return Boolean.FALSE;
        }
    }
}

